﻿#include "channel.h"
#include <sys/epoll.h>
#include <unistd.h>
#include "eventloop.h"

Channel::Channel(EventLoop *eloop, int fd)
    : m_eloop(eloop), m_fd(fd), m_events(0), m_revents(0)
{}

// Channel只对文件描述符进行监控，因此析构时不能close(fd)
Channel::~Channel()
{}


// 获取描述符
int Channel::getFd() const
{
    return m_fd;
}

// 获取事件
uint32_t Channel::getEvents() const
{
    return m_events;
}

// 获取就绪事件
uint32_t Channel::getRevents() const
{
    return m_revents;
}



// 设置就绪事件
void Channel::setRevents(uint32_t revents)
{
    m_revents = revents;
}

// 更新监控
void Channel::update()
{
    m_eloop->updateChannel(this);
}

// 移除监控
void Channel::remove()
{
    m_eloop->removeChannel(this);
}

// 是否可读
bool Channel::isReadAble() const
{
    return m_events & EPOLLIN;
}

// 是否可写
bool Channel::isWriteAble() const
{
    return m_events & EPOLLOUT;
}

// 添加可读监控
void Channel::enableRead()
{
    m_events |= EPOLLIN;
    update();
}

// 添加可写监控
void Channel::enableWrite()
{
    m_events |= EPOLLOUT;
    update();
}

// 关闭可读监控
void Channel::disableRead()
{
    m_events &= ~EPOLLIN;
    update();
}

// 关闭可写监控
void Channel::disableWrite()
{
    m_events &= ~EPOLLOUT;
    update();
}

// 关闭所有监控
void Channel::disableAll()
{
    m_events = 0;
    update();
}

// 设置回调函数
void Channel::setReadCallback(const EventCallback &callback)
{
    m_read_callback = callback;
}

void Channel::setWriteCallback(const EventCallback &callback)
{
    m_write_callback = callback;
}

void Channel::setErrorCallback(const EventCallback &callback)
{
    m_error_callback = callback;
}

void Channel::setCloseCallback(const EventCallback &callback)
{
    m_close_callback = callback;
}

void Channel::setAnyCallback(const EventCallback &callback)
{
    m_any_callback = callback;
}

// 处理事件
void Channel::handleEvent()
{
    // 可读处理：有数据写入、对方关闭连接、有紧急数据处理
    if(m_revents & EPOLLIN || m_revents & EPOLLPRI || m_revents & EPOLLRDHUP)
    {
        if(m_read_callback)
        {
            m_read_callback();
        }
    }
    // 可写处理：有数据可写
    if(m_revents & EPOLLOUT)
    {
        if(m_write_callback)
        {
            m_write_callback();
        }
    }
    else if(m_revents & EPOLLERR)
    {
        if(m_error_callback)
        {
            m_error_callback();
        }
    }
    else if(m_revents & EPOLLHUP)
    {
        if(m_close_callback)
        {
            m_close_callback();
        }
    }

    // NOTE: 任意事件回调, 作用是刷新连接的最后活跃时间
    if(m_any_callback)
    {
        m_any_callback();
    }
}

